package com.candy.common.controller;

import cn.hutool.core.lang.tree.Tree;
import cn.hutool.core.lang.tree.TreeNodeConfig;
import cn.hutool.core.lang.tree.TreeUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.IService;
import com.candy.common.entity.IdDTO;
import com.candy.common.entity.TreeEntity;
import com.candy.common.result.R;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.apache.commons.lang3.StringUtils;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import javax.servlet.http.HttpServletRequest;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

/**
 * controller基类，service注入不能用@Resource
 *
 * @author Lenovo
 * @param <T>
 */
@Slf4j
public class BaseController<S extends IService<T>, T>
{
	@Autowired
	protected S baseService;

	public static Page getPage()
	{
		HttpServletRequest request = ((ServletRequestAttributes)RequestContextHolder.getRequestAttributes()).getRequest();
		int page = 1;
		String strPage = request.getParameter("page");
		if(StringUtils.isNotEmpty(strPage))
		{
			page= Integer.valueOf(strPage);
		}
		int limit = 10;
		String strlimit = request.getParameter("limit");
		if (StringUtils.isNotEmpty(strlimit))
		{
			limit = Integer.valueOf(strlimit);
		}
		return new Page(page, limit);
	}

	@ApiOperation(value = "列表")
	@GetMapping("/list")
	public R list(@RequestBody T t)
	{
		QueryWrapper queryWrapper = new QueryWrapper();
		queryWrapper.setEntity(t);
		IPage pageModel = baseService.page(getPage(), queryWrapper);
		return R.success(pageModel);
	}

	@ApiOperation(value = "详情")
	@GetMapping(value = "/detail")
	public R getInfo(@RequestBody IdDTO idDTO)
	{
		Long id = Long.valueOf(idDTO.getId().toString());
		return R.success(baseService.getById(id));
	}

	@ApiOperation(value = "新增")
	@PostMapping("/save")
	public R save(@Validated @RequestBody T t)
	{
		return R.success(baseService.save(t));
	}

	@ApiOperation(value = "新增")
	@PostMapping("/saveBatch")
	public R saveBatch(@Validated @RequestBody Collection<T> entityList)
	{
		return R.success(baseService.saveBatch(entityList));
	}

	@ApiOperation(value = "修改")
	@PutMapping("/edit")
	public R edit(@Validated @RequestBody T t)
	{
		return R.success(baseService.updateById(t));
	}

	@ApiOperation(value = "批量修改")
	@PutMapping("/editBatch")
	public R editBatch(@Validated @RequestBody Collection<T> entityList)
	{
		return R.success(baseService.updateBatchById(entityList));
	}

	@ApiOperation(value = "删除")
	@DeleteMapping("delete")
	public R remove(@RequestBody IdDTO idDTO)
	{
		if(idDTO.getId()!=null)
		{
			Long id = Long.valueOf(idDTO.getId().toString());
			return R.success(baseService.removeById(id));
		}
		else if(idDTO.getIds()!=null && !idDTO.getIds().isEmpty())
		{
			List<Object> ids = idDTO.getIds();
			List<Long> idList = new ArrayList<>();
			for (Object id : ids)
			{
				idList.add(Long.valueOf(id.toString()));
			}
			return R.success(baseService.removeByIds(idList));
		}
		else
		{
			return R.error("未获取到要删除的数据");
		}
	}

	@ApiOperation(value = "树列表")
	@GetMapping("/tree")
	public R tree(T t)
	{
		if(t instanceof TreeEntity)
		{
			TreeEntity treeEntity = (TreeEntity) t;
			QueryWrapper<T> queryWrapper = new QueryWrapper<>();
			queryWrapper.setEntity(t);
			List<T> organzationList = baseService.list();
			//配置
			TreeNodeConfig treeNodeConfig = new TreeNodeConfig();
			// 自定义属性名 都要默认值的
			treeNodeConfig.setWeightKey("orderNum");
			treeNodeConfig.setNameKey("title");
			treeNodeConfig.setIdKey("id");
			treeNodeConfig.setParentIdKey("pid");
			treeNodeConfig.setChildrenKey("children");
			// 最大递归深度
			treeNodeConfig.setDeep(3);

			//转换器
			List<Tree<Long>> treeNodes = TreeUtil.build(organzationList, 0L, treeNodeConfig,
					(treeNode, tree) -> {
						tree.setId(treeEntity.getId());
						tree.setParentId(treeEntity.getPid());
						tree.setWeight(treeEntity.getOrderNum());
						tree.setName(treeEntity.getName());
					});
			return R.success(treeNodes);
		}
		return R.error("当前对象不是树结构");
	}
}